#pragma once

#include "../../jsonxx/json.hpp"
#include "ast.hpp"

static const string NAME = "Type";
static const string CHILDREN = "Children";

static void my_to_json(FifoJson &fifoJ, const PtrASTNode &ast) {
    fifoJ[NAME] = ast->name;
    for (auto [key, val] : ast->fields) {
        string str;
        for (auto j : val)
            str += j.word;
        fifoJ[key] = str;
    }
    vector<FifoJson> children;
    for (auto i = ast->children.begin(); i != ast->children.end(); ++i) {
        FifoJson tmp;
        my_to_json(tmp, *i);
        children.push_back(tmp);
    }
    if (!children.empty())
        fifoJ[CHILDREN] = children;
}

static void my_from_json(const FifoJson &j, PtrASTNode &ast) {
    j[NAME] = ast->name;
    vector<FifoJson> children;
    if (j.count(CHILDREN))
        children = j[CHILDREN].as_array();
    for (auto i : children) {
        PtrASTNode tmp = make_shared<ASTNode>();
        my_from_json(i, tmp);
        ast->children.push_back(tmp);
    }
    for (auto [key, val] : j.as_object()) {
        if (key != CHILDREN) { // 处理fields
            Token token;
            token.word = val.as_string();
            ast->fields[key].push_back(token);
        }
    }
}

FifoJson my_json_wrap(const PtrASTNode &ast){
    FifoJson ret;
    my_to_json(ret, ast);
    return ret;
}

